﻿//+-------------------------------------------------------------------------------------------------------------------------------------------------------
//
//Description: data contract classes for the settings obtained from Azure to be applied to the plugin handlers

//Copyright © Microsoft Corporation
//Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. 
//You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 
//
//THIS CODE IS PROVIDED *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED, 
//INCLUDING WITHOUT LIMITATION ANY IMPLIED WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABLITY OR NON-INFRINGEMENT. 
//See the Apache Version 2.0 License for specific language governing permissions and limitations under the License.
// 
//--------------------------------------------------------------------------------------------------------------------------------------------------------
using System;
using System.Collections.Generic;
using System.Runtime.Serialization;

namespace VmroleAuthor.Models
{

    /// <summary>
    /// This class defines a data contract for the settings obtained from Azure to be applied to the plugin handlers.
    /// </summary>
    [DataContract]
    class AzureExtensionConfig
    {
        /// <summary>
        /// Azure Extension Handler settings.
        /// </summary>
        [DataMember(IsRequired = true, EmitDefaultValue = false)]
        internal AzureExtensionHandlerSettings[] RuntimeSettings = null;
    }

    [DataContract]
    class AzureExtensionHandlerSettings
    {
        [DataMember(IsRequired = true, EmitDefaultValue = false)]
        internal AzureExtensionSettings HandlerSettings = null;
    }

    [DataContract]
    class AzureExtensionSettings
    {
        /// <summary>
        /// Encrypted private settings.
        /// </summary>
        [DataMember(IsRequired = false, EmitDefaultValue = false)]
        internal string protectedSettings = null;

        /// <summary>
        /// Thumbprint that should be used to decrypt the private settings.
        /// </summary>
        [DataMember(IsRequired = false, EmitDefaultValue = false)]
        internal string protectedSettingsCertThumbprint = null;

        ///// <summary>
        ///// Public settings.
        ///// </summary>
        [DataMember(IsRequired = false, EmitDefaultValue = false)]
        internal object publicSettings = null;
    }

    [DataContract]
    class AzureExtensionHandlerPrivateSettings
    {
        [DataMember(IsRequired = true, EmitDefaultValue = false)]
        internal AzureExtensionHandlerV1Settings VMMEHV1 = null;
    }

    public enum GoalStateMessageAction
    {
        Converge,
        Retry,
        Skip,
        Commit,
        SeedGoalState
    }

    [DataContract]
    class AzureExtensionHandlerV1Settings 
    {
        /// <summary>
        /// An input to the handler indicating the type of action required.
        /// </summary>
        public GoalStateMessageAction Mode; // Not Serialized over the wire 
        [DataMember(IsRequired = true, EmitDefaultValue = false, Name = "Mode", Order = 1)]
        public string ModeString
        {
            get { return this.Mode.ToString(); }
            set
            {               
                if (!Enum.TryParse(value, true, out this.Mode))
                {                 
                    throw new ApplicationException("Mode Value unexpected " + value);
                }
            }
        }

        public NodeCategoryType NodeType; // Not Serialized over the wire 
        [DataMember(IsRequired = true, EmitDefaultValue = false, Name = "NodeType", Order = 2)]
        public string NodeTypeString
        {
            get { return this.NodeType.ToString(); }
            set
            {
                if (!Enum.TryParse(value, true, out this.NodeType))
                {
                    throw new ApplicationException("NodeType Value unexpected " + value);                  
                }
            }
        }

        [DataMember(IsRequired = true, EmitDefaultValue = false, Order = 3)]
        public string Name { get; set; }
        [DataMember(IsRequired = true, EmitDefaultValue = false, Order = 4)]
        public string Version { get; set; }
        [DataMember(IsRequired = true, EmitDefaultValue = false, Order = 5)]
        public string Publisher { get; set; }
        [DataMember(IsRequired = true, EmitDefaultValue = false, Order = 6)]
        public string SchemaVersion { get; set; }
        [DataMember(IsRequired = true, EmitDefaultValue = false, Order = 7)]
        public string Type { get; set; }
        [DataMember(IsRequired = false, EmitDefaultValue = false, Order = 8)]
        public EHV1DataPackage DataPackage { get; set; }
        [DataMember(IsRequired = true, EmitDefaultValue = false, Order = 9)]
        public EHV1ApplicationProfile ApplicationProfile { get; set; }

        public AzureExtensionHandlerV1Settings(string mode, string nodeType, VMRoleResourceExtensionDefinition resextObj)
        {
            this.ModeString = mode;
            this.NodeTypeString = nodeType;

            this.Name = resextObj.Name;
            this.Version = resextObj.Version;
            this.Publisher = resextObj.Publisher;
            this.SchemaVersion = resextObj.SchemaVersion;
            this.Type = resextObj.Type;
            if (resextObj.DataPackage != null)
            {
                this.DataPackage = new EHV1DataPackage(resextObj.DataPackage);
            }
            this.ApplicationProfile = new EHV1ApplicationProfile(resextObj.ExtensionSettings.ApplicationProfile);
        }
    }

    [DataContract]
    public class EHV1DataPackage
    {
        [DataMember(IsRequired = true, EmitDefaultValue = false)]
        public string Version { get; set; }
        [DataMember(IsRequired = true, EmitDefaultValue = false)]
        public string Location { get; set; }

        public EHV1DataPackage(DataPackage package)
        {
            this.Version = package.Version;
            this.Location = package.Location;
        }
    }


    [DataContract]
    public class EHV1ApplicationProfile
    {
        [DataMember(IsRequired = true, EmitDefaultValue = false)]
        public string Name { get; set; }
        [DataMember(IsRequired = false, EmitDefaultValue = false)]
        public List<ApplicationPayload> ApplicationPayload { get; set; }
        [DataMember(IsRequired = false, EmitDefaultValue = false)]
        public WindowsApplicationProfile WindowsApplicationProfile { get; set; }

        public EHV1ApplicationProfile(ApplicationProfile appProfile)
        {
            this.Name = appProfile.Name;
            this.ApplicationPayload = appProfile.ApplicationPayload;
            this.WindowsApplicationProfile = appProfile.WindowsApplicationProfile;
        }
    }

    public enum NodeCategoryType
    {
        /// <remarks/>
        First,

        /// <remarks/>
        Last,

        /// <remarks/>
        Rest,
    }

}